/**
 * 超深度上下文Prompt增强器（Unit Test）
 * 
 * 基于ultra-deep-context学习数据，为UT生成提供：
 * 1. 真实项目的测试函数实现示例
 * 2. Mock使用模式和完整示例
 * 3. 头文件推荐和依赖分析
 * 4. GN配置推荐
 */

import * as fs from 'fs';
import * as path from 'path';

interface TestContext {
    testFile: string;
    testClass?: string;
    testFunction: string;
    testBody: string;
    mockUsage: string[];
    assertions: string[];
    includes: string[];
    testedFunction?: string;
    buildGn?: string;
}

interface MockContext {
    mockFile: string;
    mockClass?: string;
    mockMethods: string[];
    includes: string[];
    baseClass?: string;
    mockPatterns: string[];
}

interface UltraDeepIndex {
    stats: any;
    sourceToTestMapping: Record<string, string[]>;
    sourceToFuzzMapping: Record<string, string[]>;
    gnRelationships: any[];
    testBatches: number;
    fuzzBatches: number;
    mockBatches: number;
}

export class UltraDeepPromptEnhancer {
    private static knowledgeDir = path.join(__dirname, '../../../core/knowledge');
    private static index: UltraDeepIndex | null = null;
    private static testContextsCache: TestContext[] = [];
    private static mockContextsCache: MockContext[] = [];
    
    /**
     * 初始化：加载索引文件
     */
    private static loadIndex(): UltraDeepIndex {
        if (this.index) {
            return this.index;
        }
        
        const indexPath = path.join(this.knowledgeDir, 'ultra-deep-index.json');
        if (fs.existsSync(indexPath)) {
            this.index = JSON.parse(fs.readFileSync(indexPath, 'utf-8'));
            return this.index as UltraDeepIndex;
        }
        
        console.warn('[UltraDeepPromptEnhancer] 索引文件不存在，将使用基础Prompt');
        return {
            stats: {},
            sourceToTestMapping: {},
            sourceToFuzzMapping: {},
            gnRelationships: [],
            testBatches: 0,
            fuzzBatches: 0,
            mockBatches: 0
        };
    }
    
    /**
     * 加载测试上下文（懒加载，只加载需要的批次）
     */
    private static loadTestContexts(maxSamples: number = 100): TestContext[] {
        if (this.testContextsCache.length > 0) {
            return this.testContextsCache.slice(0, maxSamples);
        }
        
        const index: UltraDeepIndex = this.loadIndex();
        const contexts: TestContext[] = [];
        
        // 加载前2个批次（2000个测试文件）
        const batchesToLoad = Math.min(2, index.testBatches);
        for (let i = 0; i < batchesToLoad; i++) {
            const batchPath = path.join(this.knowledgeDir, `ultra-deep-test-${i}.json`);
            if (fs.existsSync(batchPath)) {
                const batch = JSON.parse(fs.readFileSync(batchPath, 'utf-8'));
                contexts.push(...batch);
            }
        }
        
        this.testContextsCache = contexts;
        return contexts.slice(0, maxSamples);
    }
    
    /**
     * 加载Mock上下文（懒加载）
     */
    private static loadMockContexts(maxSamples: number = 50): MockContext[] {
        if (this.mockContextsCache.length > 0) {
            return this.mockContextsCache.slice(0, maxSamples);
        }
        
        const index: UltraDeepIndex = this.loadIndex();
        const contexts: MockContext[] = [];
        
        // 加载前1个批次（500个Mock文件）
        const batchesToLoad = Math.min(1, index.mockBatches);
        for (let i = 0; i < batchesToLoad; i++) {
            const batchPath = path.join(this.knowledgeDir, `ultra-deep-mock-${i}.json`);
            if (fs.existsSync(batchPath)) {
                const batch = JSON.parse(fs.readFileSync(batchPath, 'utf-8'));
                contexts.push(...batch);
            }
        }
        
        this.mockContextsCache = contexts;
        return contexts.slice(0, maxSamples);
    }
    
    /**
     * 核心方法：增强UT生成Prompt
     */
    public static enhancePrompt(
        basePrompt: string,
        sourceCode: string,
        functionName?: string
    ): string {
        console.log(`\n🔮 [UltraDeepPromptEnhancer] 开始增强Prompt...`);
        
        const index: UltraDeepIndex = this.loadIndex();
        if (!index || !this.index || index.testBatches === 0) {
            console.warn('[UltraDeepPromptEnhancer] 未找到学习数据，使用基础Prompt');
            return basePrompt;
        }
        
        // 1. 分析源码特征
        const features = this.analyzeSourceFeatures(sourceCode, functionName);
        console.log(`   特征分析: 包含${features.includes.length}个头文件, ${features.functionCalls.length}个函数调用`);
        
        // 2. 查找相似的测试示例
        const similarTests = this.findSimilarTests(features, 5);
        console.log(`   找到${similarTests.length}个相似测试示例`);
        
        // 3. 查找相关的Mock示例
        const mockExamples = this.findRelevantMocks(features, 3);
        console.log(`   找到${mockExamples.length}个Mock示例`);
        
        // 4. 构建增强Prompt
        let enhancedPrompt = basePrompt;
        
        // 添加真实项目的测试函数示例
        if (similarTests.length > 0) {
            enhancedPrompt += '\n\n## 📚 真实项目的测试函数示例（供参考学习）\n\n';
            enhancedPrompt += '以下是OpenHarmony项目中的真实测试代码，请参考其风格和模式：\n\n';
            
            similarTests.forEach((test, idx) => {
                enhancedPrompt += `### 示例${idx + 1}：${test.testClass || 'TestClass'}::${test.testFunction}\n\n`;
                enhancedPrompt += '```cpp\n';
                // 截取前80行避免Prompt过长
                const lines = test.testBody.split('\n').slice(0, 80);
                enhancedPrompt += lines.join('\n');
                if (test.testBody.split('\n').length > 80) {
                    enhancedPrompt += '\n    // ... 更多测试逻辑 ...\n';
                }
                enhancedPrompt += '\n```\n\n';
                
                // 关键信息提取
                if (test.mockUsage.length > 0) {
                    enhancedPrompt += `**Mock用法**: ${test.mockUsage.slice(0, 3).join(', ')}\n\n`;
                }
                if (test.assertions.length > 0) {
                    enhancedPrompt += `**断言类型**: ${test.assertions.slice(0, 3).join(', ')}\n\n`;
                }
            });
        }
        
        // 添加Mock使用模式
        if (mockExamples.length > 0) {
            enhancedPrompt += '\n\n## 🎭 Mock使用模式（必须遵循）\n\n';
            enhancedPrompt += '以下是OpenHarmony项目中常用的Mock模式，请严格遵循：\n\n';
            
            mockExamples.forEach((mock, idx) => {
                enhancedPrompt += `### Mock示例${idx + 1}：${mock.mockClass || 'MockClass'}\n\n`;
                enhancedPrompt += '```cpp\n';
                enhancedPrompt += `// 文件: ${path.basename(mock.mockFile)}\n`;
                if (mock.baseClass) {
                    enhancedPrompt += `// 继承自: ${mock.baseClass}\n`;
                }
                enhancedPrompt += `\n`;
                mock.mockMethods.slice(0, 5).forEach(method => {
                    enhancedPrompt += `${method}\n`;
                });
                if (mock.mockMethods.length > 5) {
                    enhancedPrompt += `// ... 更多${mock.mockMethods.length - 5}个Mock方法 ...\n`;
                }
                enhancedPrompt += '```\n\n';
                
                if (mock.mockPatterns.length > 0) {
                    enhancedPrompt += `**常用模式**: ${mock.mockPatterns.slice(0, 3).join(', ')}\n\n`;
                }
            });
        }
        
        // 添加头文件推荐
        const recommendedHeaders = this.recommendHeaders(features);
        if (recommendedHeaders.length > 0) {
            enhancedPrompt += '\n\n## 📦 推荐的头文件（基于类似测试）\n\n';
            enhancedPrompt += '```cpp\n';
            recommendedHeaders.forEach(header => {
                enhancedPrompt += `#include ${header}\n`;
            });
            enhancedPrompt += '```\n\n';
        }
        
        // 添加关键提示
        enhancedPrompt += '\n\n## ⚠️ 关键要求（必须严格遵守）\n\n';
        enhancedPrompt += '1. **完整性**: 生成的测试代码必须包含所有必要的头文件，不允许省略\n';
        enhancedPrompt += '2. **Mock使用**: 如需Mock，请参考上述示例的Mock模式，确保Mock类和方法正确声明\n';
        enhancedPrompt += '3. **测试覆盖**: 每个测试用例应覆盖不同的分支和边界条件\n';
        enhancedPrompt += '4. **断言充分**: 使用EXPECT_EQ、EXPECT_NE、EXPECT_TRUE等断言验证所有关键返回值和状态\n';
        enhancedPrompt += '5. **资源清理**: 如有资源分配，必须在测试结束前释放\n';
        enhancedPrompt += '6. **HWTEST_F宏**: 使用标准的HWTEST_F(TestClass, TestName, TestSize.Level1)格式\n\n';
        
        console.log(`✅ [UltraDeepPromptEnhancer] Prompt增强完成！`);
        console.log(`   原始长度: ${basePrompt.length} 字符`);
        console.log(`   增强后长度: ${enhancedPrompt.length} 字符 (+${enhancedPrompt.length - basePrompt.length})\n`);
        
        return enhancedPrompt;
    }
    
    /**
     * 分析源码特征
     */
    private static analyzeSourceFeatures(sourceCode: string, functionName?: string): any {
        const features = {
            includes: [] as string[],
            functionCalls: [] as string[],
            classes: [] as string[],
            keywords: [] as string[],
            functionName: functionName
        };
        
        // 提取include
        const includeRegex = /#include\s+[<"]([^>"]+)[>"]/g;
        let match;
        while ((match = includeRegex.exec(sourceCode)) !== null) {
            features.includes.push(match[1]);
        }
        
        // 提取函数调用（简单模式）
        const callRegex = /\b([A-Z][a-zA-Z0-9_]*)::[a-zA-Z0-9_]+\(/g;
        while ((match = callRegex.exec(sourceCode)) !== null) {
            features.classes.push(match[1]);
        }
        
        // 提取关键字
        if (sourceCode.includes('std::shared_ptr')) features.keywords.push('shared_ptr');
        if (sourceCode.includes('std::unique_ptr')) features.keywords.push('unique_ptr');
        if (sourceCode.includes('std::vector')) features.keywords.push('vector');
        if (sourceCode.includes('std::string')) features.keywords.push('string');
        if (sourceCode.includes('nullptr')) features.keywords.push('nullptr');
        
        return features;
    }
    
    /**
     * 查找相似的测试示例
     */
    private static findSimilarTests(features: any, limit: number = 5): TestContext[] {
        const tests = this.loadTestContexts(200);
        
        // 计算相似度并排序
        const scored = tests.map(test => {
            let score = 0;
            
            // 头文件匹配
            const commonIncludes = test.includes.filter(inc => 
                features.includes.some((f: string) => f.includes(inc) || inc.includes(f))
            );
            score += commonIncludes.length * 3;
            
            // 类名匹配
            const commonClasses = features.classes.filter((cls: string) => 
                test.testBody.includes(cls)
            );
            score += commonClasses.length * 5;
            
            // 关键字匹配
            const commonKeywords = features.keywords.filter((kw: string) => 
                test.testBody.includes(kw)
            );
            score += commonKeywords.length * 2;
            
            // Mock使用情况匹配
            if (test.mockUsage.length > 0) {
                score += 10; // 优先推荐有Mock的测试
            }
            
            // 测试函数长度（偏好中等长度，50-200行）
            const bodyLines = test.testBody.split('\n').length;
            if (bodyLines >= 50 && bodyLines <= 200) {
                score += 5;
            }
            
            return { test, score };
        });
        
        // 按分数排序并返回
        return scored
            .filter(item => item.score > 0)
            .sort((a, b) => b.score - a.score)
            .slice(0, limit)
            .map(item => item.test);
    }
    
    /**
     * 查找相关的Mock示例
     */
    private static findRelevantMocks(features: any, limit: number = 3): MockContext[] {
        const mocks = this.loadMockContexts(100);
        
        // 计算相关性
        const scored = mocks.map(mock => {
            let score = 0;
            
            // 头文件匹配
            const commonIncludes = mock.includes.filter(inc => 
                features.includes.some((f: string) => f.includes(inc) || inc.includes(f))
            );
            score += commonIncludes.length * 3;
            
            // Mock方法数量（偏好方法适中的Mock类）
            if (mock.mockMethods.length >= 3 && mock.mockMethods.length <= 15) {
                score += 5;
            }
            
            // Mock模式丰富度
            score += mock.mockPatterns.length * 2;
            
            return { mock, score };
        });
        
        return scored
            .filter(item => item.score > 0)
            .sort((a, b) => b.score - a.score)
            .slice(0, limit)
            .map(item => item.mock);
    }
    
    /**
     * 推荐头文件
     */
    private static recommendHeaders(features: any): string[] {
        const tests = this.loadTestContexts(100);
        const headerFrequency = new Map<string, number>();
        
        // 统计相似测试中的头文件频率
        tests.forEach(test => {
            test.includes.forEach(inc => {
                headerFrequency.set(inc, (headerFrequency.get(inc) || 0) + 1);
            });
        });
        
        // 推荐高频头文件
        const recommended = Array.from(headerFrequency.entries())
            .filter(([header]) => {
                // 过滤掉已存在的头文件
                return !features.includes.some((f: string) => f === header);
            })
            .sort((a, b) => b[1] - a[1])
            .slice(0, 10)
            .map(([header]) => {
                // 格式化为include语句
                if (header.startsWith('<') || header.startsWith('"')) {
                    return header;
                }
                return `<${header}>`;
            });
        
        return recommended;
    }
}

